package com.example.redis.controller;

import com.alibaba.fastjson2.JSON;
import com.example.redis.utils.RedisUtil;
import jakarta.annotation.Resource;
import lombok.Getter;
import lombok.Setter;
import lombok.experimental.Accessors;
import org.springframework.cache.annotation.CacheConfig;
import org.springframework.cache.annotation.CacheEvict;
import org.springframework.cache.annotation.CachePut;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.web.bind.annotation.*;

import java.io.Serial;
import java.io.Serializable;
import java.util.Optional;

@CacheConfig(cacheNames = "userCache")
@RestController
@RequestMapping("/redis")
public class RedisController {

    @Resource
    private RedisUtil redisUtil;

    @Getter
    @Setter
    @Accessors(chain = true)
    public static class UserDTO implements Serializable {
        @Serial
        private static final long serialVersionUID = -2482109463155419335L;

        private String uniqueId;
        private String username;
        private String password;
        private Integer age;
    }

    @Cacheable(key = "#uniqueId")
    @GetMapping("/getUserDTO/{uniqueId}")
    public UserDTO getUserDTO(@PathVariable String uniqueId) {
        System.out.println("从缓存中获取数据" + uniqueId);
        UserDTO userDTO = new UserDTO();
        userDTO.setUniqueId("123456")
                .setUsername("admin")
                .setPassword("123456")
                .setAge(25);
        return userDTO;
    }


    @Cacheable(key = "#userDTO.uniqueId")
    @PostMapping("/insert")
    public UserDTO insert(@RequestBody UserDTO userDTO) {
//        String data = JSON.toJSONString(userDTO);
        redisUtil.set("测试Redis分布式缓存", userDTO);
        return userDTO;
    }

    @CacheEvict(key = "#uniqueId")
    @DeleteMapping("/delete")
    public String delete(@RequestParam String uniqueId) {
        return "hello world";
    }

    @CachePut(key = "#userDTO.uniqueId")
    @PutMapping("/update")
    public UserDTO update(@RequestBody UserDTO userDTO) {
        return userDTO;
    }

    @GetMapping("/select/{key}")
    public void select(@PathVariable String key) {
        redisUtil.get(key);
        Object object = Optional.ofNullable(redisUtil.get(key)).orElseThrow();
        System.out.println(object);
        String jsonString = JSON.toJSONString(object);
        System.out.println(jsonString);
    }

}

// springboot 中使用 redis 缓存注解参考官网 https://java.cunzaima.cn/spring-boot_docs_3.2.3-zh-all/io.html#io
// 一个 Cache 缓存的键的组成格式为 prefix + cacheName + key 三部分组成，其中 prefix 为缓存键的前缀，cacheName 就是 @CacheConfig 中配置的 cacheNames，key 就是方法参数或者方法返回值。
// 例如：@Cacheable(cacheNames = "userCache", key = "#userId")，则最终的缓存键为：userCache:12345